package com.itheima.train.manager.mq;

import com.alibaba.fastjson.JSON;
import com.itheima.train.manager.domain.Order;
import com.itheima.train.manager.domain.SynSeatInfo;
import com.itheima.train.manager.domain.TbRidingPlanDate;
import com.itheima.train.manager.utils.BeanMapConverter;
import com.rabbitmq.client.Channel;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.BoundHashOperations;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.util.Set;

@Service
public class RedisConsumer {

    // 创建一个日志对象
    private Logger logger = LoggerFactory.getLogger(RedisConsumer.class) ;

    @Autowired
    private StringRedisTemplate redisTemplate ;

    @Autowired(required = false)
    private BeanMapConverter beanMapConverter ;

    // @RabbitListener(queues = "syn_seat_to_redis_queue")
    public void synSeat(String seatInfo , Message message , Channel channel) {

        try {

            // 将数据解析成指定的对象
            SynSeatInfo synSeatInfo = JSON.parseObject(seatInfo , SynSeatInfo.class) ;

            // train_seat:train_num:date:seatNature:coachNum coachNum 车厢号  seatNum 0 .....
            String synSeatKey = "train_seat:" + synSeatInfo.getTrainNum() + ":" + synSeatInfo.getDate() + ":" + synSeatInfo.getSeatNature() + ":" + synSeatInfo.getCoachNum() ;

            // 缓存数据
            redisTemplate.boundHashOps(synSeatKey).put("coach_num" , String.valueOf(synSeatInfo.getCoachNum()));
            redisTemplate.boundHashOps(synSeatKey).put(synSeatInfo.getSeatNum() , "0");

            logger.info("【同步座位的数据获取成功了】---->" + seatInfo);

            // 手动应答
            // channel.basicAck(message.getMessageProperties().getDeliveryTag() , false);

        } catch (Exception e) {
            e.printStackTrace();
            logger.error("【同步座位的数据获取失败了】---->" + seatInfo);
        }

    }

    @RabbitListener(queues = "syn_riding_plan_to_redis_queue")
    public void synRidingPlan(String synRidingPlan , Message message , Channel channel) {

        try {

            // 将数据解析成指定的对象
            TbRidingPlanDate tbRidingPlanDate = JSON.parseObject(synRidingPlan , TbRidingPlanDate.class) ;

            // riding_plan:train_num:date:id id value busSeatStock 168  firstSeatStock 200 ...
            String synRidingPlanKey = "riding_plan:" + tbRidingPlanDate.getTrainNum() + ":" + tbRidingPlanDate.getTrainRidingDate() + ":" + tbRidingPlanDate.getId() ;
            redisTemplate.boundHashOps(synRidingPlanKey).putAll(beanMapConverter.beanToMap(tbRidingPlanDate));

            logger.info("【同步乘车计划获取成功了】---->" + synRidingPlan);

            // 手动应答
            // channel.basicAck(message.getMessageProperties().getDeliveryTag() , false);

        } catch (Exception e) {
            e.printStackTrace();
            logger.error("【同步乘车计划获取失败了】---->" + synRidingPlan);
        }

    }

    @RabbitListener(queues = "back_stock_redis_queue")
    public void backStock(String orderJson , Message message , Channel channel) {


        try {

            // 库存回退
            logger.error("【Redis回退库存开始了】 ---> " + orderJson);
            Order order = JSON.parseObject(orderJson , Order.class) ;
            String stockCountKeyDynamic = "riding_plan:" + order.getTrainNum() + ":" + order.getTrainRidingDate() + ":*"  ;
            Set<String> keys = redisTemplate.keys(stockCountKeyDynamic);
            for(String key : keys) {
                BoundHashOperations<String, Object, Object> boundHashOperations = redisTemplate.boundHashOps(key);
                switch (order.getSeatNature()) {
                    case "3" :
                        int firstSeatStock = Integer.parseInt(boundHashOperations.get("firstSeatStock").toString());
                        boundHashOperations.put("firstSeatStock" , String.valueOf(firstSeatStock + 1));
                        break;
                    case "4" :
                        int secondSeatStock = Integer.parseInt(boundHashOperations.get("secondSeatStock").toString()) ;
                        boundHashOperations.put("secondSeatStock" , String.valueOf(secondSeatStock + 1));
                        break ;
                    case "7" :
                        int hardSleeperStock = Integer.parseInt(boundHashOperations.get("hardSleeperStock").toString()) ;
                        boundHashOperations.put("hardSleeperStock" , String.valueOf(hardSleeperStock + 1));
                        break ;
                    case "6" :
                        int softSleeperStock = Integer.parseInt(boundHashOperations.get("softSleeperStock").toString()) ;
                        boundHashOperations.put("softSleeperStock" , String.valueOf(softSleeperStock + 1));
                        break ;
                    case "2" :
                        int busSeatStock = Integer.parseInt(boundHashOperations.get("busSeatStock").toString()) ;
                        boundHashOperations.put("busSeatStock" , String.valueOf(busSeatStock + 1));
                        break ;
                    case "5" :
                        int hardSeatStock = Integer.parseInt(boundHashOperations.get("hardSeatStock").toString()) ;
                        boundHashOperations.put("hardSeatStock" , String.valueOf(hardSeatStock + 1));
                        break ;
                    case "9" :
                        int softSeatStock = Integer.parseInt(boundHashOperations.get("softSeatStock").toString()) ;
                        boundHashOperations.put("softSeatStock" , String.valueOf(softSeatStock + 1));
                        break ;
                }
            }

            logger.info("【Redis回退库存成功了】 ---> " + orderJson);

            // 释放座位
            logger.info("【Redis释放座位开始了】 ---> " + orderJson);
            String seatNatureKey = "train_seat:" + order.getTrainNum() + ":" + order.getTrainRidingDate() + ":" + order.getSeatNature() + ":" + order.getCoachNum() ;
            redisTemplate.boundHashOps(seatNatureKey).put(order.getSeatNum() , "0");
            logger.info("【Redis释放座位成功了】 ---> " + orderJson);

            // 给出应答
            channel.basicAck(message.getMessageProperties().getDeliveryTag() , false);

        } catch (IOException e) {
            e.printStackTrace();
            logger.error("【Redis回退库存失败】 ---> " + orderJson);
        }

    }

}
